﻿using System;
using System.ComponentModel;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Controls.Primitives;
using System.Windows.Data;
using System.Windows.Media;
using System.Windows.Media.Animation;

namespace QDP.Platform.Silverlight.Controls
{
    [TemplatePart(Name = KEY_PART_ExpandController, Type = typeof(ToggleButton))]
    [TemplatePart(Name = KEY_PART_Content, Type = typeof(Canvas))]
    public class TileGroupContainer : Control, INotifyPropertyChanged
    {
        const string KEY_PART_ExpandController = "PART_ExpandController";
        const string KEY_PART_Content = "PART_Content";

        public TileGroupContainer()
        {
            this.DefaultStyleKey = typeof(TileGroupContainer);

            var res = Application.Current.Resources;
            if (res.Contains("TileWidth"))
                tile_width = (double)res["TileWidth"];
            if (res.Contains("TileHeight"))
                tile_height = (double)res["TileHeight"];
            if (res.Contains("TileSpan"))
                tile_span = (double)res["TileSpan"];
        }

        private ToggleButton PART_ExpandController;
        private Canvas PART_Content;
        private string _Header = string.Empty;

        private double tile_width = 80;
        private double tile_height = 80;
        private double tile_span = 5;
        private TileGroupObject Group;

        public override void OnApplyTemplate()
        {
            base.OnApplyTemplate();
            Group = this.DataContext as TileGroupObject;
            if (Group == null) return;

            this.PART_ExpandController = base.GetTemplateChild(KEY_PART_ExpandController) as ToggleButton;
            this.PART_Content = base.GetTemplateChild(KEY_PART_Content) as Canvas;

            if (this.PART_Content != null)
            {
                PART_Content.Width = 0;
                PART_Content.Height = tile_height * 2 + tile_span * 3;
                int row1_null_block = 0;
                int row2_null_block = 0;

                #region 填充磁贴组
                foreach (var tile in Group.Children)
                {
                    double x = 0, y = 0;
                    if (tile.RowSpan > 2)
                    {
                        tile.RowSpan = 2;
                    }
                    if (tile.New)
                    {
                        row1_null_block = row2_null_block = Math.Max(row1_null_block, row2_null_block);
                    }

                    if (tile.RowSpan == 2)
                    {
                        #region 处理占两行的磁贴
                        y = tile_span;
                        if (row1_null_block - row2_null_block < 0)
                        {
                            x = row2_null_block * (tile_width + tile_span);
                            row1_null_block = row2_null_block;
                        }
                        else
                            x = row1_null_block * (tile_width + tile_span);

                        row2_null_block = row1_null_block += tile.ColumnSpan;
                        #endregion //#region 处理占两行的磁贴
                    }
                    else
                    {
                        #region 处理占一行的磁贴
                        if (row1_null_block - row2_null_block <= 0) // 显示在第一行
                        {
                            #region 处理显示在第一行的磁贴
                            y = tile_span;
                            x = row1_null_block * (tile_width + tile_span);
                            row1_null_block += tile.ColumnSpan;
                            #endregion //#region 处理显示在第一行的磁贴
                        }
                        else if (row1_null_block - row2_null_block > 0)
                        {
                            #region 处理显示在第二行的磁贴
                            y = tile_span*2 + tile_height;
                            x = row2_null_block * (tile_width + tile_span);
                            row2_null_block += tile.ColumnSpan;
                            #endregion //#region 处理显示在第二行的磁贴
                        }
                        #endregion //#region 处理占一行的磁贴
                    }

                    var element = new Button()
                    {
                        Width = (tile_width * tile.ColumnSpan) + tile_span * (tile.ColumnSpan - 1),
                        Height = (tile_height * tile.RowSpan) + tile_span * (tile.RowSpan - 1),
                        Content = tile.Caption,
                        DataContext = tile.Navigation,
                    };
                    if (tile.Navigation.TileTemplate != null)
                        element.Template = tile.Navigation.TileTemplate;
                    else
                    {
                        element.Command = tile.Navigation.Command;
                        element.Template = Application.Current.Resources["TileButton"] as ControlTemplate;
                    }
                    element.SetBinding(Button.BackgroundProperty, new Binding()
                    {
                        Source = tile.Navigation.Navigation,
                        Path = new PropertyPath("Background"),
                        FallbackValue = Application.Current.Resources["TileBrush"] as Brush,
                        TargetNullValue = Application.Current.Resources["TileBrush"] as Brush
                    });
                    element.SetBinding(Button.ForegroundProperty, new Binding()
                    {
                        Source = tile.Navigation.Navigation,
                        Path = new PropertyPath("Foreground"),
                        FallbackValue = Application.Current.Resources["TextBrush"] as Brush,
                        TargetNullValue = Application.Current.Resources["TextBrush"] as Brush
                    });
                    Canvas.SetLeft(element, x);
                    Canvas.SetTop(element, y);
                    PART_Content.Children.Add(element);
                }//foreach (var tile in group.Children)

                if (row1_null_block < row2_null_block)
                {
                    row1_null_block = row2_null_block;
                }
                else
                {
                    row2_null_block = row1_null_block;
                }

                this.MaxWidth = PART_Content.Width += (tile_width + tile_span) * row1_null_block - tile_span;
                this.MaxWidth += 30;
                #endregion //#region 填充磁贴组
            }
            if (this.PART_ExpandController != null)
            {
                PART_ExpandController.Checked += PART_ExpandController_Checked;
                PART_ExpandController.Unchecked += PART_ExpandController_Unchecked;
                PART_ExpandController.SetBinding(ToggleButton.IsCheckedProperty, new Binding()
                {
                    Path = new PropertyPath("IsExpanded"),
                    Mode = BindingMode.TwoWay,
                });
                PART_ExpandController.Content = Group.Caption;

                if (IsEnabled)
                {
                    this.ChangeExpandedStatus();
                }
            }
        }

        void PART_ExpandController_Unchecked(object sender, RoutedEventArgs e)
        {
            this.ChangeExpandedStatus();
        }

        void PART_ExpandController_Checked(object sender, RoutedEventArgs e)
        {
            this.ChangeExpandedStatus();
        }

        private void ChangeExpandedStatus()
        {
            Storyboard story = new Storyboard();
            var canvas = this.PART_Content;
            var framesw = new DoubleAnimationUsingKeyFrames();
            Storyboard.SetTarget(framesw, this);
            Storyboard.SetTargetProperty(framesw, new PropertyPath("Width"));
            var span = canvas.MaxWidth / 1000;
            if (span > 0.3) span = 0.3;
            if (span < 0) span = 0.1;
            
            double width = double.IsInfinity(this.MaxWidth) ? 0 : this.MaxWidth;
            if (PART_ExpandController.IsChecked == true)
            {
                framesw.KeyFrames.Add(new EasingDoubleKeyFrame
                {
                    Value = 30,
                    KeyTime = KeyTime.FromTimeSpan(TimeSpan.FromSeconds(0))
                });
                framesw.KeyFrames.Add(new EasingDoubleKeyFrame
                {
                    Value = width,
                    KeyTime = KeyTime.FromTimeSpan(TimeSpan.FromSeconds(span))
                });
            }
            else
            {
                framesw.KeyFrames.Add(new EasingDoubleKeyFrame
                {
                    Value = width,
                    KeyTime = KeyTime.FromTimeSpan(TimeSpan.FromSeconds(0))
                });
                framesw.KeyFrames.Add(new EasingDoubleKeyFrame
                {
                    Value = 30,
                    KeyTime = KeyTime.FromTimeSpan(TimeSpan.FromSeconds(span))
                });
            }
            story.Children.Add(framesw);
            story.Begin();
        }

        #region INotifyPropertyChanged
        public event PropertyChangedEventHandler PropertyChanged;
        protected void NotifyPropertyChanged(object sender, String propertyName)
        {
            if (PropertyChanged != null)
                PropertyChanged(sender, new PropertyChangedEventArgs(propertyName));
        }
        #endregion //#region INotifyPropertyChanged
    }
}